/**
  * Author: Mei
  * Date: 2020-12-10 20:44
  * Description: 变化的模板  变化的是个数和类型
  *
  */
#include "../head.h"

using namespace std;

void print() {
}

int flag = 1;

template<typename T, typename ...Args>
void print(const T &a, const Args &...args) {
    if (flag == 1) {
        cout << a;
        flag = 0;
    } else {
        cout << "," << a;
    }
    print(args...);
};

template<int idx, int max, typename... Args>
struct PRINT_TUPLE {
    static void print(ostream &os, const tuple<Args...> &t) {
        os << get<idx>(t) << (idx + 1 == max ? "" : ", ");
        PRINT_TUPLE<idx + 1, max, Args...>::print(os, t);
    }
};

template<int max, typename... Args>
struct PRINT_TUPLE<max, max, Args...> { //当PRINT_TUPLE<a,b,max> 中a==b时  调用这个版本的特例化
    static void print(ostream &os, const tuple<Args...> &t) {
    }
};

template<typename ...Args>
ostream &operator<<(ostream &out, const tuple<Args...> &t) {
    out << "[";
    PRINT_TUPLE<0, sizeof...(Args), Args...>::print(out, t);
    out << "]";
    return out;
}

template<int a, int b, int c>
class col2 {
public:
    void show() {
        cout << a << ", " << ", " << endl;
    }
};

template<int a,int b>
class col2<1, a, b> { //只要第一个传入1 就会调用这个版本的偏特化
public:
    void show() {
        cout << "partical specialization" << a << ", " << a << endl;
    }
};
template<>
class col2<4, 3, 4> {
public:
    void show() {
        cout << "full specialization" <<  endl;
    }
};

/**********************************/

template<typename T, typename K, typename S>
class col {
public:
    void show(T a) {
        cout << a << ", " << ", " << endl;
    }
};

template<>
class col<int, int, int> {
public:
    void show(int a) {
        cout << a << ", " << a << endl;
    }
};


int main() {
    //cout << "[";
    //print(2.3, "adfdf", bitset<5>(4), 22);
    //cout << "]";
    auto result = make_tuple(1.5, "123", " aa", bitset<5>(2));  //打成一包东西 不同数据类型的返回值
    cout << get<3>(result) << endl;

    cout << make_tuple(1.5, "123", " aa", bitset<5>(2)) << endl;

    col<int, double, int> cc;
    col<int, int, int> cc1; //调用三个类型都是int的特化
    cc.show(1);


    col2<5, 3, 4> dd;
    col2<1, 3, 4> dd2;  //偏特化
    col2<4, 3, 4> dd3; //全特化
    dd.show();
    /**
     * 特例化版本（特化）的范围一定要小于泛化的范围
     */


    return 0;
}

